#include "head.h"

int main(int argc,char* argv[])
{
    if(argc!=4)
    {
        printf("./process_pool IP PORT PROCESS_NUM\n");
        return -1;
    }
    //创建子进程
    int childNum=atoi(argv[3]);
    processData_t *workerList=(processData_t*)calloc(childNum,sizeof(processData_t));
    makechild(workerList,childNum);

    //父进程处理网络连接
    int sersockfd;
    tcp_init(argv[1],argv[2],&sersockfd);

    //监控sersockfd和子进程的socket一端
    int epfd=epoll_create(1);
    epoll_add(epfd,sersockfd);
    // printf("epoll success\n");
    //监控子进程的管道对端
    int i;
    for(i=0;i<childNum;i++)
    {
        epoll_add(epfd,workerList[i].pipeFd);
#ifdef DEBUG
        printf("add workerList[%d].pipeFd %d\n",i,workerList[i].pipeFd);
#endif
    }

    struct epoll_event* evs=(struct epoll_event*)calloc(childNum+1,sizeof(struct epoll_event));
    int ready_fd_num,j,finish_flag=0;
    struct sockaddr_in clientAddr;
    int clientlen=sizeof(clientAddr);

    while(1){
        ready_fd_num=epoll_wait(epfd,evs,childNum+1,-1);
        for(i=0;i<ready_fd_num;i++){
            //表明有客户端连接上了
            if(evs[i].data.fd==sersockfd)
            { 
                int new_fd=accept(sersockfd,(struct sockaddr*)&clientAddr,&clientlen);
                ERROR_CHECK(new_fd,-1,"accept");
                printf("client coming, IP %s port %d\n",inet_ntoa(clientAddr.sin_addr),
                    clientAddr.sin_port);
                //发给子进程
                for(j=0;j<childNum;j++)
                {
                    if(workerList[j].status==FREE)
                    { //发给空闲的子进程 假设一定能找到空闲的子进程
                        sendFd(workerList[j].pipeFd,new_fd);
                        workerList[j].status=BUSY;
                        printf("%d 任务派给 %d 子进程\n",new_fd,workerList[j].pid);
                        break;
                    }
                }
                close(new_fd);
            }else{ //子进程通知父进程完成任务
                for(j=0;j<childNum;j++)
                {
                    if(evs[i].data.fd==workerList[j].pipeFd)
                    {
                        read(workerList[j].pipeFd,&finish_flag,sizeof(int));
                        printf("Child %d process finish %d!\n",workerList[j].pid,finish_flag);
                        workerList[j].status=FREE;
                        break;
                    }
                }
            }
        }
    }
    while(1);
}